#ifndef B2D_OBJECTFACTORY_H
#define B2D_OBJECTFACTORY_H

#include "IResource.h"

NS_B2D_BEGIN

////////////////////////////////////////////////////////////////////////////////////////////////////
/// \brief	Interface for a resource factory.
/// 		Note: do not derive from IResourceFactory directly, derive from BaseResourceFactory<T>
////////////////////////////////////////////////////////////////////////////////////////////////////
class B2D_API IResourceFactory
	: public IUncopyable
{
	B2D_INTERFACE(IResourceFactory)

public:
	////////////////////////////////////////////////////////////////////////////////////////////////////
	/// \brief	Get the type of resource it handles.
	///
	/// \return	The resource type.
	////////////////////////////////////////////////////////////////////////////////////////////////////
	virtual const ObjectType& getResourceType(void) const = 0;

	////////////////////////////////////////////////////////////////////////////////////////////////////
	/// \brief	Gets the number of resources in the cache.
	///
	/// \return	The resource count.
	////////////////////////////////////////////////////////////////////////////////////////////////////
	virtual size_t getResourceCount(void) const = 0;
	////////////////////////////////////////////////////////////////////////////////////////////////////
	/// \brief	Searches for the resource with the given name.
	///
	/// \param	name	The name.
	///
	/// \return	The found resource.
	////////////////////////////////////////////////////////////////////////////////////////////////////
	virtual ResourcePtr findResource(const StringId& name) const = 0;

_internal:
	////////////////////////////////////////////////////////////////////////////////////////////////////
	/// \brief	Adds an existing resource to the cache. If a resource already exists with the same name
	/// 		as this resource it will be replaced.
	///
	/// \param	r	The resource to add.
	////////////////////////////////////////////////////////////////////////////////////////////////////
	virtual void _addResourceToCache(const ResourcePtr& r) = 0;
	////////////////////////////////////////////////////////////////////////////////////////////////////
	/// \brief	Removes the resource with the given name from the cache if it exists.
	///
	/// \param	id	The identifier.
	////////////////////////////////////////////////////////////////////////////////////////////////////
	virtual void _removeResourceFromCache(const StringId& id) = 0;
	////////////////////////////////////////////////////////////////////////////////////////////////////
	/// \brief	Creates an empty resouce of the type managed by this factory. The name is optional if
	/// 		addToCache=false.
	///
	/// \param	name	  	The name.
	/// \param	addToCache	true to add to cache.
	///
	/// \return	The new empty resource.
	////////////////////////////////////////////////////////////////////////////////////////////////////
	virtual ResourcePtr _createEmpty(const string& name, bool addToCache) = 0;
	////////////////////////////////////////////////////////////////////////////////////////////////////
	/// \brief	Creates a resource from a file and optionally adds it to the cache.
	///
	/// \param	path	  	Path of the file.
	/// \param	addToCache	true to add to cache.
	///
	/// \return	The new resource.
	////////////////////////////////////////////////////////////////////////////////////////////////////
	virtual ResourcePtr _createFromFile(const string& path, bool addToCache) = 0;
	////////////////////////////////////////////////////////////////////////////////////////////////////
	/// \brief	Gets a resource with the given path as a name. If the resurce doesn't exist, the
	/// 		factory tries to create and load it from the given path.
	///
	/// \param	path	Path of the resource file.
	///
	/// \return	The resource if successful.
	////////////////////////////////////////////////////////////////////////////////////////////////////
	virtual ResourcePtr _getOrCreateFromFile(const string& path) = 0;
	////////////////////////////////////////////////////////////////////////////////////////////////////
	/// \brief	Clears the cache.
	////////////////////////////////////////////////////////////////////////////////////////////////////
	virtual void _clearCache(void) = 0;
	////////////////////////////////////////////////////////////////////////////////////////////////////
	/// \brief	Clears the unreferenced resources from the cache.
	////////////////////////////////////////////////////////////////////////////////////////////////////
	virtual void _clearUnreferenced(void) = 0;
};

NS_B2D_END

#endif